import { isFunction } from '../utils/index.js'
import { effect, track, trigger } from './effect.js'

export function computed(getterOrOption) {
    let getter, setter
    if (isFunction(getterOrOption)) {
        // 是函数的情况
        getter = getterOrOption
        setter = () => {
            console.warn('computed is readonly')
        }
    } else {
        // 是对象的情况
        getter = getterOrOption.get
        setter = getterOrOption.set
    }
    return new ComputedImpl(getter, setter)
}

class ComputedImpl {
    constructor(getter, setter) {
        this._setter = setter
        this._value = undefined
        // 脏值标致依赖是否更新,依赖更新_dirty=true
        this._dirty = true
        this.effect = effect(getter, {
            lazy: true,
            scheduler: () => {
                if (!this._dirty) {
                    this._dirty = true
                    trigger(this, 'value')
                }
            }
        })
    }
    get value() {
        if (this._dirty) {
            // 重新计算值
            this._value = this.effect()
            this._dirty = false
            track(this, 'value')
        }
        return this._value
    }
    set value(newValue) {
        // todo 
        this._setter(newValue)
    }
}

